package com.wootion.cims.config.filter;

import java.io.ByteArrayInputStream;
import java.io.IOException;

import javax.servlet.ReadListener;
import javax.servlet.ServletInputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;

import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.text.StringEscapeUtils;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;

import cn.hutool.http.HTMLFilter;

public class XssHttpServletRequestWrapper extends HttpServletRequestWrapper {
	
	private final static HTMLFilter html_filter = new HTMLFilter();

	public XssHttpServletRequestWrapper(HttpServletRequest request) {
		super(request);
	}

	@Override
	public String[] getParameterValues(String name) {
		String[] values = super.getParameterValues(name);
		if(values!=null) {
			int length = values.length;
			String[] escapseValues =new String[length];
			for (int i = 0; i < length; i++) {
				escapseValues[i] =  html_filter.filter(values[i].trim());
			}
			return escapseValues;
		}
		return super.getParameterValues(name);
	}
	@Override
	public ServletInputStream getInputStream() throws IOException {
		
		String content_type = super.getHeader(HttpHeaders.CONTENT_TYPE);
		
		if(!(MediaType.APPLICATION_JSON_VALUE.equalsIgnoreCase(content_type)||MediaType.APPLICATION_JSON_UTF8_VALUE.equalsIgnoreCase(content_type))) {
			return super.getInputStream();
		}
		String json = IOUtils.toString(super.getInputStream(),"utf-8");
		if(StringUtils.isBlank(json)) {
			return super.getInputStream();
		}
		json = html_filter.filter(json);
		json = StringEscapeUtils.unescapeHtml4(json);
		final ByteArrayInputStream bis = new ByteArrayInputStream(json.getBytes("utf-8")); 
		return new ServletInputStream() {
			
			@Override
			public int read() throws IOException {
				return bis.read();
			}
			
			@Override
			public void setReadListener(ReadListener listener) {
			}
			
			@Override
			public boolean isReady() {
				return true;
			}
			
			@Override
			public boolean isFinished() {
				return true;
			}
		};
	}
}
